package org.flexharmony.ant;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.DirectoryScanner;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.Task;
import org.apache.tools.ant.types.FileSet;
import org.flexharmony.harmonizer.ClassFilesHarmonizer;
import org.flexharmony.harmonizer.config.HarmonyConfiguration;

public class HarmonizeTask extends Task
{
  private String flexSrcDirName;
  
  private Boolean additiveOnly;
  
  private List<FileSet> fileSets = new ArrayList<FileSet>();
  
  public HarmonizeTask()
  {}

  public void setFlexSrcDir(String flexSrcDirName)
  {
    this.flexSrcDirName = flexSrcDirName;
  }
  
  public void setAdditiveOnly(Boolean additiveOnly)
  {
    this.additiveOnly = additiveOnly;
  }

  public void addFileSet(FileSet fileset)
  {
    fileSets.add(fileset);
  }

  public void execute() throws BuildException
  {
    if (flexSrcDirName == null)
    {
      throw new BuildException("Flex source directory attribute (flexSrcDir) must be specified.");
    }
    
    File flexSourceDir = new File(flexSrcDirName);
    if (!flexSourceDir.isDirectory())
    {
      throw new BuildException("Invalid flex source directory: " + flexSrcDirName);
    }
    
    if (fileSets.size() == 0)
    {
      throw new BuildException("At least on fileset sub-element is required (for class files location).");
    }
    
    HarmonyConfiguration configuration = new HarmonyConfiguration();
    configuration.setFlexSrcDir(flexSourceDir);
    if (additiveOnly != null) configuration.setAdditiveOnly(additiveOnly);
    
    ClassFilesHarmonizer classFilesHarmonizer = new ClassFilesHarmonizer(configuration);
    try
    {
      for (FileSet fileSet : fileSets)
      {
        DirectoryScanner scanner = fileSet.getDirectoryScanner();
        File dirBase = scanner.getBasedir();
        
        log("Processing fileset at base dir " + dirBase.getAbsolutePath(), Project.MSG_DEBUG);
        
        String[] fileNames = scanner.getIncludedFiles();
        
        List<File> classFiles = new ArrayList<File>();
        for (String fileName : fileNames)
        {
          String filePath = dirBase + File.separator + fileName;
          if (filePath.endsWith(".class"))
          {
            log("  Including class file " + filePath, Project.MSG_DEBUG);
            classFiles.add(new File(filePath));
          }
        }
        
        if (classFiles.size() > 0)
        {
          classFilesHarmonizer.harmonize(classFiles);
        }
      }
      log("Total classes harmonized: " + classFilesHarmonizer.getTotalClassesHarmonized(), Project.MSG_INFO);
      log("Total classes updated: " + classFilesHarmonizer.getTotalClassesUpdated(), Project.MSG_INFO);
    }
    catch (IOException ioexc)
    {
      throw new BuildException(ioexc);
    }
  }
}
